# -*- coding: utf-8 -*-
# time: 2025/8/9 16:17
# file: serializers.py
# author: kai
# email: 1071664616@qq.com

"""
用户序列化
"""
from rest_framework import serializers
from rest_framework_simplejwt.serializers import TokenObtainPairSerializer
from rest_framework_simplejwt.views import TokenObtainPairView
from django.contrib.auth import authenticate
from rest_framework_simplejwt.tokens import RefreshToken

from .models import User


class AdminTokenObtainPairSerializer(serializers.Serializer):
    """
    管理员用户名+密码登录序列化器
    """
    username = serializers.CharField()
    password = serializers.CharField(write_only=True)

    def validate(self, attrs):
        username = attrs.get('username')
        password = attrs.get('password')

        # 查找管理员用户
        try:
            # 由于 USERNAME_FIELD 是 phone_number，我们需要同时检查 username 和 phone_number
            # 先尝试通过 username 查找
            try:
                user = User.objects.get(username=username, user_type='admin')
            except User.DoesNotExist:
                # 如果通过 username 找不到，再尝试通过 phone_number 查找
                user = User.objects.get(phone_number=username, user_type='admin')
        except User.DoesNotExist:
            raise serializers.ValidationError('管理员账户不存在')

        # 验证密码
        if not user.check_password(password):
            raise serializers.ValidationError('密码错误')
        
        # 生成token
        refresh = RefreshToken.for_user(user)
        
        data = {
            'refresh_token': str(refresh),
            'access': str(refresh.access_token),
            'username': user.username,
            'user_type': user.user_type,
            'phone_number': user.phone_number,
            'avatar': user.avatar.url if user.avatar else None
        }

        return data

class AdminTokenObtainPairView(TokenObtainPairView):
    serializer_class = AdminTokenObtainPairSerializer

class CustomTokenObtainPairSerializer(TokenObtainPairSerializer):
    @classmethod
    def get_token(cls, user):
        token = super().get_token(user)

        # 添加自定义claims
        token['username'] = user.username
        token['user_type'] = user.user_type
        token['phone_number'] = user.phone_number

        return token

# class CustomTokenObtainPairView(TokenObtainPairView):
#     serializer_class = CustomTokenObtainPairSerializer

class UserSerializer(serializers.ModelSerializer):
    class Meta:
        model = User
        fields = [
            'id', 'username', 'user_type', 'phone_number', 'avatar', 'created_at'
        ]
        read_only_fields = ['id', 'created_at']
        ref_name = 'UserDetail'

class UserListSerializer(serializers.ModelSerializer):
    """
    用户列表序列化器，不包含敏感信息
    """
    class Meta:
        model = User
        fields = [
            'id', 'username', 'user_type', 'phone_number', 'avatar', 'created_at', 'is_active'
        ]
        ref_name = 'UserList'

class PhoneAuthSerializer(serializers.Serializer):
    """
    手机号验证码认证序列化器
    """
    phone_number = serializers.CharField(help_text='手机号')
    input_verification_code = serializers.CharField(help_text='验证码')

    def validate_phone_number(self, value):
        if not value:
            raise serializers.ValidationError("手机号不能为空")
        return value

class UserProfileSerializer(serializers.ModelSerializer):
    """
    用户个人信息序列化器
    """
    class Meta:
        model = User
        fields = [
            'id', 'username', 'user_type', 'phone_number', 'avatar', 'created_at', 'is_active', 'last_login'
        ]
        read_only_fields = ['id', 'username', 'user_type', 'created_at']
        ref_name = 'UserProfile'


class AdminCreateSerializer(serializers.ModelSerializer):
    """
    管理员创建序列化器
    """
    password = serializers.CharField(write_only=True, min_length=6)

    class Meta:
        model = User
        fields = [
            'id', 'username', 'phone_number', 'password', 'avatar'
        ]
        read_only_fields = ['id']

    def create(self, validated_data):
        password = validated_data.pop('password')
        user = User(**validated_data)
        user.set_password(password)
        user.user_type = 'admin'
        user.save()
        return user